﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web;
using FlexiCommerce.Persistence;
using FlexiCommerce.Security;
using FlexiCommerce.Web;
using FlexiCommerce.Localization;

namespace FlexiCommerce.Engine
{
    public interface IEngine
    {


        ISecurityManager SecurityManager { get; }
        IWebContext RequestContext { get; }
        IPersister Persister { get; }
        ILocalizationManager LocalizationManager {get;}
        IUrlParser UrlParser { get; }
        /// <summary>
        /// Initialize components and plugins in the FlexiCommerce CMS environment.
        /// </summary>
        void Initialize();

        /// <summary>Resolves a service configured for the factory.</summary>
        /// <typeparam name="T">The type of service to resolve.</typeparam>
        /// <returns>An instance of the resolved service.</returns>
        T Resolve<T>() where T : class;

        /// <summary>Resolves a service configured for the factory.</summary>
        /// <param name="serviceType">The type of service to resolve.</param>
        /// <returns>An instance of the resolved service.</returns>
        object Resolve(Type serviceType);

        /// <summary>Resolves a named service configured for the factory.</summary>
        /// <param name="key">The name of the service to resolve.</param>
        /// <returns>An instance of the resolved service.</returns>
        object Resolve(string key);

        /// <summary>Registers a component in the IoC container.</summary>
        /// <param name="key">The name of the component.</param>
        /// <param name="classType">The type of component.</param>
        void AddComponent(string key, Type classType);

        /// <summary>Registers a component in the IoC container.</summary>
        /// <param name="key">The name of the component.</param>
        /// <param name="serviceType">The service interface of the component.</param>
        /// <param name="classType">The type of component.</param>
        void AddComponent(string key, Type serviceType, Type classType);

        /// <summary>Adds a compnent instance to the container.</summary>
        /// <param name="key">A unique key.</param>
        /// <param name="serviceType">The type of service to provide.</param>
        /// <param name="instance">The service instance to add.</param>
        void AddComponentInstance(string key, Type serviceType, object instance);

        /// <summary>Adds a compnent instance to the container.</summary>
        /// <param name="instance">The service instance to add.</param>
        T AddComponentInstance<T>(T instance) where T : class;

        /// <summary>Adds a "facility" to the IoC container. Unless this has been changed it's assumed that tihs is a <see cref="Castle.MicroKernel.IFacility"/>.</summary>
        /// <param name="key">The name of the facility.</param>
        /// <param name="facility">The facility instance.</param>
        void AddFacility(string key, object facility);

        /// <summary>Releases a component from the IoC container.</summary>
        /// <param name="instance">The component instance to release.</param>
        void Release(object instance);


    }
}
